/*
	proc_CPU_monitor.c

	contains the CPU monitor system process functionality

	Author: Aidan Goddard 25/7/13
*/

#include"../setup/headers/printf.h"
#include"headers/scheduler_functions.h"
#include"headers/process_control.h"
#include"../klib/headers/klib_proc_threads.h"
#include"../klib/headers/klib_ACDM.h"
#include"../klib/headers/klib_system_resources.h"


/*
	process entry point
*/

static HWND hwnd;
static char *buff;

static uint64_t monitor_thread(void *data)
{
	// control variables
	int pos = 0;
	char c = 32;

	// main loop
	while(1)
	{
		// wait a bit
		__KLIB__SleepThisThread(100000);

		// can write up to 79th char on the 11th line
		pos++;
		if(pos > 959)
		{
			pos = 0;
			if(c > 0)
			{
				c = 0;
			}
			else
			{
				c = 32;
			}
		}

		// check char to write
		if(c > 0)
		{
			c++;
			if(c > 122)
			{
				c = 33;
			}
		}

		// write the new char to the new pos
		buff[pos * 2] = c;

		// update the screen
		ACDMWindowUpdate(hwnd);
	}



	// finished
	__KLIB__KillThisThread(0);
	return 0;
}


void proc_system_CPU_monitor(void)
{
	// wait 5 seconds for everything to initialise
	SleepMe(5000000);

	// create a window
	hwnd = ACDMCreateStaticWindow(__KLIB__RCGetPID(), "multi-threading demo 2", 22);
	ACDMWindowShow(hwnd);
	buff = (char*)ACDMWindowGetBufferAddress(hwnd);

	// clear the screen buffer
	int i;
	for(i = 0; i < 3680; i += 2)
	{
		buff[i] = 0;
		buff[i + 1] = 0x1f;
	}

	// create a worker thread
	__KLIB__SpawnNewThread(monitor_thread, NULL, (void*)(KOFFSET + 0x3a80000));

	// control variables
	int pos = 960;
	char c = 32;

	// main loop
	while(1)
	{
		// wait a bit
		__KLIB__SleepThisThread(50000);

		// can write up to 79th char on the 22nd line
		pos++;
		if(pos > 1839)
		{
			pos = 960;
			if(c > 0)
			{
				c = 0;
			}
			else
			{
				c = 32;
			}
		}

		// check char to write
		if(c > 0)
		{
			c++;
			if(c > 122)
			{
				c = 33;
			}
		}

		// write the new char to the new pos
		buff[pos * 2] = c;

		// update the screen
		ACDMWindowUpdate(hwnd);
	}


	KillThisProcess(0);
	//KillThisThread(0);
	return;
}
